package gdut.bsx.share2;

import android.app.Activity;
import android.content.ComponentName;
import android.content.Intent;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager;
import android.content.pm.ResolveInfo;
import android.net.Uri;
import android.os.Build;
import android.support.annotation.NonNull;
import android.text.TextUtils;
import android.util.Log;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;

/**
 * Share2
 *
 * @author baishixian
 * @date 2018/3/29 11:00
 */

public class Share2 {

    private static final String TAG = "Share2";

    /**
     * Current activity
     */
    private Activity activity;

    /**
     * Share content type
     */
    private @ShareContentType
    String contentType;

    /**
     * Share title
     */
    private String title;

    /**
     * Share file Uri
     */
    private Uri shareFileUri;

    /**
     * Share content text
     */
    private String contentText;

    /**
     * Share to special component PackageName
     */
    private String componentPackageName;

    /**
     * Share to special component ClassName
     */
    private String componentClassName;

    /**
     * Share complete onActivityResult requestCode
     */
    private int requestCode;

    /**
     * Forced Use System Chooser
     */
    private boolean forcedUseSystemChooser;

    private String p1, p2, p3, p4, p5, p6, p7, appName;

    private Share2(@NonNull Builder builder) {
        this.activity = builder.activity;
        this.contentType = builder.contentType;
        this.title = builder.title;
        this.shareFileUri = builder.shareFileUri;
        this.contentText = builder.textContent;
        this.componentPackageName = builder.componentPackageName;
        this.componentClassName = builder.componentClassName;
        this.requestCode = builder.requestCode;
        this.forcedUseSystemChooser = builder.forcedUseSystemChooser;

        this.p1 = builder.p1;
        this.p2 = builder.p2;
        this.p3 = builder.p3;
        this.p4 = builder.p4;
        this.p5 = builder.p5;
        this.p6 = builder.p6;
        this.p7 = builder.p7;
        this.appName = builder.appName;

    }

    /**
     * shareBySystem
     */
    public void shareBySystem(boolean isStart) {
        if (checkShareParam()) {
            Intent shareIntent = createShareIntent();

            if (shareIntent == null) {
                //                Log.e(TAG, "shareBySystem cancel.");
                return;
            }

            if (title == null) {
                title = "";
            }

            if (forcedUseSystemChooser) {
                shareIntent = Intent.createChooser(shareIntent, title);
            }
            try {
                shareIntent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION);
            } catch (Exception e) {
                e.printStackTrace();
            }
            if (isStart) {
                if (shareIntent.resolveActivity(activity.getPackageManager()) != null) {
                    try {
                        if (requestCode != -1) {
                            activity.startActivityForResult(shareIntent, requestCode);
                        } else {
                            activity.startActivity(shareIntent);
                        }
                    } catch (Exception e) {
                        e.printStackTrace();
                        //                        Log.e(TAG, Log.getStackTraceString(e));
                    }
                }
            }
        }
    }

    /**
     * 微信7.0版本号，兼容处理微信7.0版本分享到朋友圈不支持多图片的问题
     */
    private static final int VERSION_CODE_FOR_WEI_XIN_VER7 = 1380;
    /**
     * 微信包名
     */
    public static final String PACKAGE_NAME_WEI_XIN = "com.tencent.mm";

    private Intent createShareIntent() {
        Intent shareIntent = new Intent();
        try {
            if (VersionUtil.getVersionCode(activity, PACKAGE_NAME_WEI_XIN) < VERSION_CODE_FOR_WEI_XIN_VER7) {

            }
        } catch (Exception e) {
            e.printStackTrace();
        }

        shareIntent.setAction(Intent.ACTION_SEND);
        shareIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
        shareIntent.addCategory("android.intent.category.DEFAULT");

        if (!TextUtils.isEmpty(this.componentPackageName) && !TextUtils.isEmpty(componentClassName)) {
            ComponentName comp = new ComponentName(componentPackageName, componentClassName);
            shareIntent.setComponent(comp);
        }
        //        shareFileUri = Uri.parse("content://com.android.providers.media.documents/document/image%3A150736");
        switch (contentType) {
            case ShareContentType.TEXT:
                shareIntent.putExtra(Intent.EXTRA_TEXT, contentText);
                shareIntent.setType("text/plain");
                break;
            case ShareContentType.IMAGE:
            case ShareContentType.IMAGE_PNG:
            case ShareContentType.IMAGE_JPEG:
            case ShareContentType.IMAGE_JPG:
            case ShareContentType.AUDIO:
            case ShareContentType.VIDEO:
            case ShareContentType.FILE:
                shareIntent.setAction(Intent.ACTION_SEND);
                shareIntent.addCategory("android.intent.category.DEFAULT");
                shareIntent.setType(contentType);
                shareIntent.putExtra(Intent.EXTRA_STREAM, shareFileUri);
                shareIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
                shareIntent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
                shareIntent.putExtra(Intent.EXTRA_TEXT, TextUtils.isEmpty(contentText) ? appName : contentText);
                Log.d(TAG, "Share uri: " + shareFileUri.toString());

                if (Build.VERSION.SDK_INT <= Build.VERSION_CODES.KITKAT) {
                    List<ResolveInfo> resInfoList = activity.getPackageManager().queryIntentActivities(shareIntent, PackageManager.MATCH_DEFAULT_ONLY);
                    for (ResolveInfo resolveInfo : resInfoList) {
                        String packageName = resolveInfo.activityInfo.packageName;
                        activity.grantUriPermission(packageName, shareFileUri, Intent.FLAG_GRANT_READ_URI_PERMISSION);
                    }
                }
                break;
            default:
                Log.e(TAG, contentType + " is not support share type.");
                shareIntent = null;
                break;
        }
        return shareIntent;
    }


    public List<AppInfo> getShareAppInfoList() {
        Intent shareIntent = new Intent();
        shareIntent.setAction(Intent.ACTION_SEND);
        shareIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
        shareIntent.addCategory("android.intent.category.DEFAULT");

        if (!TextUtils.isEmpty(this.componentPackageName) && !TextUtils.isEmpty(componentClassName)) {
            ComponentName comp = new ComponentName(componentPackageName, componentClassName);
            shareIntent.setComponent(comp);
        }

        switch (contentType) {
            case ShareContentType.TEXT:
                shareIntent.putExtra(Intent.EXTRA_TEXT, contentText);
                shareIntent.setType("text/plain");
                break;
            case ShareContentType.IMAGE:
            case ShareContentType.IMAGE_JPEG:
            case ShareContentType.IMAGE_JPG:
            case ShareContentType.IMAGE_PNG:
            case ShareContentType.AUDIO:
            case ShareContentType.VIDEO:
            case ShareContentType.FILE:
                shareIntent.setAction(Intent.ACTION_SEND);
                shareIntent.addCategory("android.intent.category.DEFAULT");
                shareIntent.setType(contentType);
                //                shareIntent.putExtra(Intent.EXTRA_STREAM, shareFileUri);
                shareIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
                shareIntent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);

                //                Log.d(TAG, "Share uri: " + shareFileUri.toString());

                //                if (Build.VERSION.SDK_INT <= Build.VERSION_CODES.KITKAT) {
                //                    List<ResolveInfo> resInfoList = activity.getPackageManager().queryIntentActivities(shareIntent, PackageManager.MATCH_DEFAULT_ONLY);
                //                    for (ResolveInfo resolveInfo : resInfoList) {
                //                        String packageName = resolveInfo.activityInfo.packageName;
                //                        activity.grantUriPermission(packageName, shareFileUri, Intent.FLAG_GRANT_READ_URI_PERMISSION);
                //                    }
                //                }
                break;
            default:
                //                Log.e(TAG, contentType + " is not support share type.");
                shareIntent = null;
                break;
        }

        List<ResolveInfo> resInfo = activity.getPackageManager().queryIntentActivities(shareIntent, 0);
        //        List<AppInfo> appInfos = getPackages();
        List<AppInfo> tempList2 = new ArrayList<>();
        //        Log.i("info", appInfos.toString());
        //需要得到应用名称、图标、跳转包名  componentPackageName componentClassName
        AppInfo appInfo = null;
        for (int i = 0; i < resInfo.size(); i++) {
            appInfo = new AppInfo();
            appInfo.setComponentPackageName(resInfo.get(i).activityInfo.packageName);
            appInfo.setAppName(resInfo.get(i).activityInfo.loadLabel(activity.getPackageManager()).toString());
            appInfo.setComponentClassName(resInfo.get(i).activityInfo.name);
            switch (resInfo.get(i).activityInfo.name) {
                case "com.tencent.mobileqq.activity.JumpActivity":
                    appInfo.setAppName(p6);
                    appInfo.setSort(6);
                    break;
                case "com.tencent.mobileqq.activity.qfileJumpActivity":
                    appInfo.setAppName(p4);
                    appInfo.setSort(4);
                    break;
                case "cooperation.qlink.QlinkShareJumpActivity":
                    appInfo.setAppName(p1);
                    appInfo.setSort(1);
                    break;
                case "cooperation.qqfav.widget.QfavJumpActivity":
                    appInfo.setAppName(p2);
                    appInfo.setSort(2);
                    break;
                case "com.tencent.mm.ui.tools.ShareImgUI":
                    appInfo.setAppName(p7);
                    appInfo.setSort(7);
                    break;
                case "com.tencent.mm.ui.tools.AddFavoriteUI":
                    appInfo.setAppName(p3);
                    appInfo.setSort(3);
                    break;
                case "com.tencent.mm.ui.tools.ShareToTimeLineUI":
                    appInfo.setAppName(p5);
                    appInfo.setSort(5);
                    break;
                default:
                    break;
            }
            appInfo.setAppIcon(resInfo.get(i).activityInfo.loadIcon(activity.getPackageManager()));
            tempList2.add(appInfo);
        }
        Log.i("info", tempList2.toString());
        //        Toast.makeText(activity, tempList2.size() + "条", Toast.LENGTH_SHORT).show();
        //        List<ApplicationInfo> tempList = new ArrayList<>();
        //        printlnInfo(resInfo);
        //处理一下，使得微信发送给朋友、添加到微信、发送给好友、发送到朋友圈、发送到我的电脑、添加到QQ收藏、面对面快传
        Collections.sort(tempList2, new Comparator<AppInfo>() {
            @Override
            public int compare(AppInfo o1, AppInfo o2) {
                return o1.getSort() > o2.getSort() ? -1 : 1;
            }
        });
        return tempList2;
    }


    public static void main(String[] args) {
    }

    private void printlnInfo(List<ResolveInfo> resInfo) {
        if (resInfo != null) {
            if (resInfo.size() > 0) {
                for (int i = 0; i < resInfo.size(); i++) {
                    Log.i("info", "================" + i + "==================");
                    try {
                        Log.i("info", resInfo.get(i).resolvePackageName);
                    } catch (Exception e) {
                    }
                    if (resInfo.get(i).activityInfo != null) {
                        try {
                            Log.i("info activity name ", resInfo.get(i).activityInfo.loadLabel(activity.getPackageManager()) + "");
                        } catch (Exception e) {
                        }
                        Log.i("info name", resInfo.get(i).activityInfo.name);
                        Log.i("info packageName", resInfo.get(i).activityInfo.packageName);
                        if (resInfo.get(i).activityInfo.applicationInfo != null) {
                            try {
                                Log.i("info applicn foname", resInfo.get(i).activityInfo.applicationInfo.name);
                            } catch (Exception e) {
                            }
                            try {
                                //                                Log.i("info applicn package", resInfo.get(i).activityInfo.applicationInfo.packageName);
                            } catch (Exception e) {
                            }
                        }
                    }
                    Log.i("info", "================" + i + "==================");
                    Log.i("info", "                                           ");
                    Log.i("info", "                                           ");
                    Log.i("info", "                                           ");
                }
            }
        }
    }

    private List<AppInfo> getPackages() {
        // 获取已经安装的所有应用, PackageInfo　系统类，包含应用信息
        List<PackageInfo> packages = activity.getPackageManager().getInstalledPackages(0);
        List<AppInfo> mData = new ArrayList<>();
        for (int i = 0; i < packages.size(); i++) {
            PackageInfo packageInfo = packages.get(i);
            //            if ((packageInfo.applicationInfo.flags & ApplicationInfo.FLAG_SYSTEM) == 0) { //非系统应用
            // AppInfo 自定义类，包含应用信息
            AppInfo appInfo = new AppInfo();
            appInfo.setAppName(
                    packageInfo.applicationInfo.loadLabel(activity.getPackageManager()).toString());//获取应用名称
            appInfo.setPackageName(packageInfo.packageName); //获取应用包名，可用于卸载和启动应用
            appInfo.setVersionName(packageInfo.versionName);//获取应用版本名
            appInfo.setVersionCode(packageInfo.versionCode);//获取应用版本号
            appInfo.setAppIcon(packageInfo.applicationInfo.loadIcon(activity.getPackageManager()));//获取应用图标
            //            System.out.println(appInfo.toString());
            mData.add(appInfo);
            //            } else { // 系统应用
            //
            //            }
        }
        return mData;
    }

    private boolean checkShareParam() {
        if (this.activity == null) {
            //            Log.e(TAG, "activity is null.");
            return false;
        }

        if (TextUtils.isEmpty(this.contentType)) {
            //            Log.e(TAG, "Share content type is empty.");
            return false;
        }

        if (ShareContentType.TEXT.equals(contentType)) {
            if (TextUtils.isEmpty(contentText)) {
                //                Log.e(TAG, "Share text context is empty.");
                return false;
            }
        } else {
            if (this.shareFileUri == null) {
                //                Log.e(TAG, "Share file path is null.");
                return false;
            }
        }

        return true;
    }

    public static class Builder {
        private Activity activity;
        private @ShareContentType
        String contentType = ShareContentType.FILE;
        private String title;
        private String p1, p2, p3, p4, p5, p6, p7, appName;
        private String componentPackageName;
        private String componentClassName;
        private Uri shareFileUri;
        private String textContent;
        private int requestCode = -1;
        private boolean forcedUseSystemChooser = true;

        public Builder(Activity activity) {
            this.activity = activity;
        }


        public Builder setAppName(String appName) {
            this.appName = appName;
            return this;
        }

        public Builder setP1(String p1) {
            this.p1 = p1;
            return this;
        }

        public Builder setP2(String p2) {
            this.p2 = p2;
            return this;
        }

        public Builder setP3(String p3) {
            this.p3 = p3;
            return this;
        }

        public Builder setP4(String p4) {
            this.p4 = p4;
            return this;
        }

        public Builder setP5(String p5) {
            this.p5 = p5;
            return this;
        }

        public Builder setP6(String p6) {
            this.p6 = p6;
            return this;
        }

        public Builder setP7(String p7) {
            this.p7 = p7;
            return this;
        }

        /**
         * Set Content Type
         *
         * @param contentType {@link ShareContentType}
         * @return Builder
         */
        public Builder setContentType(@ShareContentType String contentType) {
            this.contentType = contentType;
            return this;
        }

        /**
         * Set Title
         *
         * @param title title
         * @return Builder
         */
        public Builder setTitle(@NonNull String title) {
            this.title = title;
            return this;
        }

        /**
         * Set share file path
         *
         * @param shareFileUri shareFileUri
         * @return Builder
         */
        public Builder setShareFileUri(Uri shareFileUri) {
            this.shareFileUri = shareFileUri;
            return this;
        }

        /**
         * Set text content
         *
         * @param textContent textContent
         * @return Builder
         */
        public Builder setTextContent(String textContent) {
            this.textContent = textContent;
            return this;
        }

        /**
         * Set Share To Component
         *
         * @param componentPackageName componentPackageName
         * @param componentClassName   componentPackageName
         * @return Builder
         */
        public Builder setShareToComponent(String componentPackageName, String componentClassName) {
            this.componentPackageName = componentPackageName;
            this.componentClassName = componentClassName;
            return this;
        }

        /**
         * Set onActivityResult requestCode, default value is -1
         *
         * @param requestCode requestCode
         * @return Builder
         */
        public Builder setOnActivityResult(int requestCode) {
            this.requestCode = requestCode;
            return this;
        }

        /**
         * Forced Use System Chooser To Share
         *
         * @param enable default is true
         * @return Builder
         */
        public Builder forcedUseSystemChooser(boolean enable) {
            this.forcedUseSystemChooser = enable;
            return this;
        }

        /**
         * build
         *
         * @return Share2
         */
        public Share2 build() {
            return new Share2(this);
        }

    }
}
